

import java.util.*;
import java.lang.*;



public class University {

	public static void main(String[] args) {	
		
		
		//Create list of students
		List<Student> studentsList = new ArrayList<Student>();
		Student s1 = new Student("Pavel","Pavloff",Sex.MALE, Speciality.PROGRAMMING);
		s1.getPersonalInfoObject().setCity("Kyiv");
		s1.getPersonalInfoObject().setDateOfBirth("10.08.1995");
		s1.getPersonalInfoObject().setStreet("Grinchenko 2/1");
		s1.getPersonalInfoObject().setZip("10027");
		Student s2 = new Student("Vika","Vikova",Sex.FEMALE, Speciality.PROGRAMMING);
		Student s3 = new Student("Olga","Olgova",Sex.FEMALE,Speciality.MUSIC);
		Student s4 = new Student("Anton","Antonov",Sex.MALE,Speciality.MUSIC);
		studentsList.add(s1);
		studentsList.add(s2);
		studentsList.add(s3);
		studentsList.add(s4);
		
		//Create list of teachers
		List<Teacher> musicTeachersList = new ArrayList<Teacher>();
		List<Teacher> programmingTeachersList = new ArrayList<Teacher>();
		Teacher t1 = new Teacher("Johann", "Bach", Sex.MALE, Subject.CHOIR);
		Teacher t2 = new Teacher("Amadeus", "Mozart", Sex.MALE, Subject.CHOIR);
		Teacher t3 = new Teacher("Viacheslav", "Krukovsky", Sex.MALE, Subject.JAVA_LANGUAGE);
		Teacher t4 = new Teacher("Aleksander", "Baglai", Sex.MALE, Subject.C_LANGUAGE);
		musicTeachersList.add(t1);
		musicTeachersList.add(t2);
		programmingTeachersList.add(t3);
		programmingTeachersList.add(t4);
		
		//Create list of groups		
		Group musicGroup = new Group(Speciality.MUSIC);
		musicGroup.setGroupName("Mus");
		musicGroup.setCurator(t1);
		Group programmersGroup = new Group(Speciality.PROGRAMMING);
		programmersGroup.setGroupName("Prog");		
		programmersGroup.setCurator(t3);
		List<Group> groupsList = new ArrayList<Group>();
		groupsList.add(programmersGroup);
		groupsList.add(musicGroup);
		
		//Create lists of students for each group
		List<Student> musicGroupStudentsList = new ArrayList<Student>();
		List<Student> programmersGroupList = new ArrayList<Student>();
		
		//split students into groups according the speciality
		for (Student student : studentsList) {	
			if(student.speciality.equals(Speciality.MUSIC)){
				musicGroupStudentsList.add(student);				
			}else{
				programmersGroupList.add(student);
			}	
		}
		//print groups
		for (Group group : groupsList) {	
			System.out.println("\nGroup '"+group.getGroupName()+"-"+group.getGroupID()+"'");
			System.out.println("Curator: "+group.curator.getPersonsFirstName());
			System.out.println("Curriculum MONDAY:");
			List<String> mondayCurriculum = group.accessToCurriculum().getCurriculum(group, DayOfWeek.MON);
			for(String subject : mondayCurriculum){
				System.out.println(subject);
			}
			System.out.println("Curriculum TUESDAY:");
			List<String> tuesdayCurriculum = group.accessToCurriculum().getCurriculum(group, DayOfWeek.TUE);
			for(String subject : tuesdayCurriculum){
				System.out.println(subject);
			}
			if(group.speciality.equals(Speciality.MUSIC)){
				System.out.println("\nMusic Teachers:");
				for (Teacher teacher : musicTeachersList) {
					teacher.printTeacherBasicInfo();
				}			
				System.out.println("\nMus Students list:");
				for (Student student : musicGroupStudentsList) {
					student.printSudentBasicInfo();
				}				
			}else{
				System.out.println("\nProgramming Teachers:");
				for (Teacher teacher : programmingTeachersList) {
					teacher.printTeacherBasicInfo();
				}	
				System.out.println("\nProg Students list:");
				for (Student student : programmersGroupList) {
					student.printSudentBasicInfo();
				}
			}		
		}	
		//print additional info
		System.out.println("\nPersonal info of the student:");
		System.out.println(s1.getPersonsFirstName()+" "+s1.getPersonsLastName()+", id = "+ s1.getID()+", "
		+s1.getPersonalInfoObject().getDateOfBirth()+", "+s1.getPersonalInfoObject().getCity()+", "
		+s1.getPersonalInfoObject().getStreet()+ ", "+s1.getPersonalInfoObject().getZip());
	}
}
	
abstract class Person
{
	private String firstName;
	private String lastName;
	Sex sex;
	private PersonalInfo personalInfo;
	private int id;
    private static int idCounter = 0;
    
    public Person(String firstName, String lastName, Sex sex){
    	this.firstName = firstName;
    	this.lastName = lastName;
    	this.sex = sex;
    	id = ++idCounter;
    }	
	public void setPersonsFirstName(String firstName){
		this.firstName = firstName;
	}
	public void setPersonsLastName(String lastName){
		this.lastName = lastName;
	}
	public String getPersonsFirstName(){
		return firstName;
	}
	public String getPersonsLastName(){
		return lastName;
	}	
	public int getID() {
        return id;
    }
	public PersonalInfo getPersonalInfoObject(){
		if (this.personalInfo == null) {
			this.personalInfo =  new PersonalInfo();
			}
		return this.personalInfo;
	}
}

class Student extends Person{
	Speciality speciality;
	
	public Student(String firstName, String lastName, Sex sex, Speciality speciality){
		super(firstName, lastName, sex);
		this.speciality = speciality;
	}
	public void printSudentBasicInfo(){
		System.out.println(this.getPersonsFirstName()+" "+this.getPersonsLastName()+
				"\nSpeciality: "+this.speciality.getSpeciality()+"\nSex:"+this.sex.getSex());
		
	}
}
class Teacher extends Person{
	Subject subject;
	
	public Teacher(String firstName, String lastName, Sex sex, Subject subject){
		super(firstName, lastName, sex);
		this.subject = subject;
	}
	public void printTeacherBasicInfo(){
		System.out.println(this.getPersonsFirstName()+" "+this.getPersonsLastName()+
				"\nSubject: "+this.subject.getSubject()+"\nSex:"+this.sex.getSex());	
	}
}
enum Sex{
	MALE("M"), FEMALE("F");
	
	private final String sex;
	
	private Sex(String sex){
		this.sex = sex;		
	}
	public String getSex(){
		return sex;
	}
}
enum Speciality{
	MUSIC("Music"), PROGRAMMING("Prog");
	
	private final String Speciality;
	
	private Speciality(String Speciality){
		this.Speciality = Speciality;		
	}
	public String getSpeciality(){
		return Speciality;
	}
}
enum Subject{
	SOLFEDGIO("Solfedgio"), CHOIR("Choir"), JAVA_LANGUAGE("Java"), C_LANGUAGE("C++");
	
	Teacher teacher;
	private final String Subject;
	
	private Subject(String Subject){
		this.Subject = Subject;		
	}
	public String getSubject(){
		return Subject;
	}
}
enum DayOfWeek{
	MON("MON"), TUE("TUE"), WED("WED");
	
	private final String DayOfWeek;
	
	private DayOfWeek(String DayOfWeek){
		this.DayOfWeek = DayOfWeek;		
	}
	public String getDayOfWeek(){
		return DayOfWeek;
	}
}
enum Auditorium{
	AUDITORIUM_01("Auditorium 01"),AUDITORIUM_02("Auditorium 02"),AUDITORIUM_03("Auditorium 03") ;
	private String Auditorium;
	
	private Auditorium(String Auditorium){
		this.Auditorium = Auditorium;
	}
	public String getAuditorium(){
		return Auditorium;
	}
}

class PersonalInfo
{
	private String zip;
	private String street;
	private String city;
	private String dateOfBirth;
	
	public String getZip() {
        return zip;
    }
    public void setZip(String zip) {
        this.zip = zip;
    }
    public String getStreet() {
		return street;
	}
    public void setStreet(String street) {
		this.street = street;
	}
	public String getCity() {
        return city;
    }
    public void setCity(String city) {
        this.city = city;
    }
    public String getDateOfBirth() {
		return dateOfBirth;
	}
    public void setDateOfBirth(String dateOfBirth) {
		this.dateOfBirth = dateOfBirth;
	}  
}
class Group {
    private String groupName;
    Teacher curator;
    Speciality speciality;
	private int groupID;
    private static int idGroupCounter = 0;
    Curriculum curriculum;
    
    public Group(Speciality speciality){	
    	this.speciality = speciality;
    	groupID = ++idGroupCounter;
    }	

    public Teacher getCurator() {
    	if (this.curator == null){
    		this.curator = new Teacher(null, null, null, null);
    	}
        return curator;
    }
    public void setCurator(Teacher curator) {
        this.curator = curator;
    }
    public String getGroupName() {
        return groupName;
    }
    public void setGroupName(String groupName) {
        this.groupName = groupName;
    }
	public int getGroupID() {
        return groupID;
    }
	public Curriculum accessToCurriculum(){
		if (this.curriculum == null) {
			this.curriculum =  new Curriculum(null, null, null, null);
			}
		return this.curriculum;
	}
}
class Curriculum{
	Subject subject;
	Auditorium auditorium;
	Group group;
	DayOfWeek dayOfWeek;
	private List<String> curriculumMusicMON = new ArrayList<String>(); 
	private List<String> curriculumProgrammingMON  = new ArrayList<String>();	
	private List<String> curriculumMusicTUE =  new ArrayList<String>(); 
	private List<String> curriculumProgrammingTUE = new ArrayList<String>();
	
	public Curriculum(List<String> curriculumMusicMON, List<String> curriculumProgrammingMON,
			List<String> curriculumMusicTUE, List<String> curriculumProgrammingTUE){
		this.curriculumMusicMON.add(Subject.SOLFEDGIO.getSubject()+", "+ Auditorium.AUDITORIUM_01.getAuditorium());	
		this.curriculumMusicMON.add(Subject.CHOIR.getSubject()+", "+ Auditorium.AUDITORIUM_02.getAuditorium());
		
		this.curriculumProgrammingMON.add(Subject.JAVA_LANGUAGE.getSubject()+", "+ Auditorium.AUDITORIUM_03.getAuditorium());
		this.curriculumProgrammingMON.add(Subject.C_LANGUAGE.getSubject()+", "+ Auditorium.AUDITORIUM_03.getAuditorium());
		
		this.curriculumMusicTUE.add(Subject.CHOIR.getSubject()+", "+ Auditorium.AUDITORIUM_02.getAuditorium());
		this.curriculumMusicTUE.add(Subject.CHOIR.getSubject()+", "+ Auditorium.AUDITORIUM_02.getAuditorium());
		
		this.curriculumProgrammingTUE.add(Subject.JAVA_LANGUAGE.getSubject()+", "+ Auditorium.AUDITORIUM_01.getAuditorium());
		this.curriculumProgrammingTUE.add(Subject.JAVA_LANGUAGE.getSubject()+", "+ Auditorium.AUDITORIUM_03.getAuditorium());	
	}	
    public List<String> getCurriculum(Group group, DayOfWeek dayOfWeek) {
    	if(group.speciality.equals(Speciality.MUSIC) && dayOfWeek.equals(dayOfWeek.MON)){
    		return curriculumMusicMON;
    	}else if(group.speciality.equals(Speciality.MUSIC) && dayOfWeek.equals(dayOfWeek.TUE)){
    		return curriculumMusicTUE;
    	} else if(group.speciality.equals(Speciality.PROGRAMMING) && dayOfWeek.equals(dayOfWeek.MON)){
    		return curriculumProgrammingMON;
    	}else{
    		return curriculumProgrammingTUE;
    	}
    	
    }
	
	
}
        